﻿using System;
using System.Collections.Generic;
using BusinessLogic.Managers.Processing.RemittanceAdvice.ValidationRules;
using BusinessLogic.Mappers;
using DataAccess.Services;

namespace BusinessLogic.Managers.Processing.RemittanceAdvice
{
	internal class RemittanceAdviceProcessor : DocumentProcessorBase<BusinessEntity.Entities.RemittanceAdvice>
	{
		private static IEnumerable<IRemittanceAdviceValidationRule> validationRules;

		private static IEnumerable<IRemittanceAdviceValidationRule> ValidationRules
		{
			get
			{
				if(validationRules == null)
				{
					validationRules = GetValidationRules();
				}

				return validationRules;
			}
		}

		protected override void Process(BusinessEntity.Entities.RemittanceAdvice remittanceAdvice, IServiceManager serviceManager)
		{
			Validate(remittanceAdvice, serviceManager);

			remittanceAdvice.IssueDate = DateTime.UtcNow;
			
			Store(remittanceAdvice, serviceManager);
		}

		protected override ProcessingExceptionCatcherBase ExceptionCatcher
		{
			get { return new RemittanceAdviceProcessingExceptionCatcher(); }
		}

		private static void Store(BusinessEntity.Entities.RemittanceAdvice remittanceAdvice, IServiceManager serviceManager)
		{
			MapperFactory.GetRemittanceAdviceMapper(serviceManager).Insert(remittanceAdvice);
		}

		private static void Validate(BusinessEntity.Entities.RemittanceAdvice remittanceAdvice, IServiceManager serviceManager)
		{
			foreach (var rule in ValidationRules)
			{
				rule.Validate(remittanceAdvice, serviceManager);
			}
		}

		private static IEnumerable<IRemittanceAdviceValidationRule> GetValidationRules()
		{
			var rules = new List<IRemittanceAdviceValidationRule>();

			rules.Add(new RemittanceAdviceNumberValidationRule());
			rules.Add(new RemittanceAdviceAccountValidationRule());
			rules.Add(new RemittanceAdvicePricingDetailsValidationRule());
			rules.Add(new RemittanceAdviceAccountingValidationRule());

			return rules;
		}
	}
}